#ifndef __PROTOCAL_HPP__
#define __PROTOCAL_HPP__

#include <cstring>
#include <string>
#include <vector>
#include<jsoncpp/json/json.h>
// 自定义协议 - 使用json封装一下

namespace QiHai
{
    static const char* SEP_BEGIN = "{";
    static const char* SEP_END = "}";
    static const int SEP_LEN = strlen(SEP_END);

    // 请求
    class Request
    {
    public:
        Request() = default;
        Request(int x, int y, char op)
        :_x(x), _y(y), _op(op)
        {}

        // 序列化
        std::string serialization()
        {
            Json::Value root;
            root["x"] = _x;
            root["y"] = _y;
            root["op"] = _op;

            Json::FastWriter writer;
            return writer.write(root);
        }

        // 反序列化
        bool deserialization(std::string request)
        {
            Json::Reader read;
            Json::Value root;
            if (!read.parse(request, root)) return false;

            _x = root["x"].asInt();
            _y = root["y"].asInt();
            _op = root["op"].asInt();
            return true;
        }

        int _x;
        int _y;
        char _op;
    };

    // 响应
    class Response
    {
    public:
        Response() = default;
        Response(int state, int result)
        :_state(state), _result(result)
        {}
        
        // 序列化
        std::string serialization()
        {
            Json::Value root;
            root["state"] = _state;
            root["result"] = _result;

            Json::FastWriter writer;
            return writer.write(root);
        }

        // 反序列化
        bool deserialization(std::string request)
        {
            Json::Reader read;
            Json::Value root;
            if (!read.parse(request, root)) return false;

            _state = root["state"].asInt();
            _result = root["result"].asInt();
            return true;
        }

        int _state;  // 状态：1正确 0异常
        int _result;  // 结果：正常就是计算结果，否则就是错误编号
    };

    // 解决粘包以及不是独立的一个报文问题：这里采用的是Json的格式{"1":1}...
    void SpliteMessage(std::string& message, std::vector<std::string>& messages)
    {
        while (true)
        {
            // 首先找到第一个{的位置
            auto begin = message.find(SEP_BEGIN);
            if (begin == std::string::npos) break;  // 没有找到一个完整报文
            auto end = message.find(SEP_END);
            if (end == std::string::npos) break;  // 同理

            std::cout << "DEBUG: " << message.substr(0, end + 1) << std::endl;
            messages.push_back(message.substr(0, end + 1));  // {}
            message.erase(0, end + SEP_LEN);
        }
    }
}

#endif